package org.springframework.ai.mcp.server.demo.tools;

import com.fasterxml.jackson.databind.ObjectMapper;
import io.modelcontextprotocol.server.McpServerFeatures;
import io.modelcontextprotocol.spec.McpSchema;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.client.RestTemplate;
import org.springframework.web.util.UriComponentsBuilder;
import org.springframework.web.util.UriUtils;

import java.net.URI;
import java.util.List;
import java.util.Map;

/**
 * 联网搜索工具配置类，提供基于SearchAPI的搜索功能。
 */
@Configuration
public class SearchToolsConfiguration {

    private static final Logger logger = LoggerFactory.getLogger(SearchToolsConfiguration.class);
    private static final int DEFAULT_NUM_RESULTS = 50;
    private static final int MAX_NUM_RESULTS = 100;

    @Value("${search.url}")
    private String searchApiUrl;

    private final RestTemplate restTemplate = new RestTemplate();
    private final ObjectMapper objectMapper = new ObjectMapper();

    /**
     * 搜索工具集合：包含所有联网搜索相关的工具。
     */
    @Bean
    public List<McpServerFeatures.SyncToolSpecification> searchTools() {
        return List.of(createSearchWebTool());
    }

    /**
     * 创建联网搜索工具。
     */
    private McpServerFeatures.SyncToolSpecification createSearchWebTool() {
        logger.info("创建联网搜索工具，API URL: {}", searchApiUrl);

        String schemaJson = """
        {
          "type": "object",
          "properties": {
            "q": {
              "type": "string",
              "description": "搜索查询内容，必填参数"
            },
            "num": {
              "type": "integer",
              "description": "返回结果数量，可选参数，默认50，最大100",
              "minimum": 1,
              "maximum": 100,
              "default": 50
            }
          },
          "required": ["q"]
        }
        """;

        McpSchema.Tool tool = new McpSchema.Tool(
            "search_web",
            "执行联网搜索并返回分页的结构化搜索结果",
            schemaJson
        );

        return new McpServerFeatures.SyncToolSpecification(
            tool,
            (exchange, arguments) -> {
                try {
                    String query = (String) arguments.get("q");
                    if (query == null || query.trim().isEmpty()) {
                        return new McpSchema.CallToolResult("错误：搜索查询内容不能为空", true);
                    }

                    Integer num = DEFAULT_NUM_RESULTS;
                    if (arguments.containsKey("num")) {
                        Object numValue = arguments.get("num");
                        if (numValue instanceof Number) {
                            num = ((Number) numValue).intValue();
                        } else if (numValue instanceof String) {
                            try {
                                num = Integer.parseInt((String) numValue);
                            } catch (NumberFormatException e) {
                                logger.warn("无效的num参数值: {}, 使用默认值: {}", numValue, DEFAULT_NUM_RESULTS);
                            }
                        }
                        // 限制结果数量在合理范围内
                        num = Math.max(1, Math.min(num, MAX_NUM_RESULTS));
                    }

                    logger.info("执行联网搜索: query='{}', num={}", query, num);

                    // 构建完整的搜索URL，使用UriComponents处理特殊字符
                    UriComponentsBuilder builder = UriComponentsBuilder.fromHttpUrl(searchApiUrl);
                    String url = builder.toUriString();

                    // 手动构建查询参数，确保正确编码
                    StringBuilder queryString = new StringBuilder();
                    queryString.append("q=").append(UriUtils.encode(query, "UTF-8"));
                    queryString.append("&num=").append(num);

                    // 如果URL已有查询参数，追加到现有参数
                    String fullUrl = url;
                    if (url.contains("?")) {
                        fullUrl = url + "&" + queryString.toString();
                    } else {
                        fullUrl = url + "?" + queryString.toString();
                    }

                    URI searchUri = URI.create(fullUrl);

                    logger.debug("搜索API请求URL: {}", searchUri);

                    // 调用搜索API
                    String response = restTemplate.getForObject(searchUri, String.class);

                    if (response == null || response.trim().isEmpty()) {
                        return new McpSchema.CallToolResult("错误：搜索API返回空结果", true);
                    }

                    // 解析并格式化结果
                    try {
                        Map<String, Object> searchResult = objectMapper.readValue(response, Map.class);

                        // 检查搜索结果状态
                        if (searchResult.containsKey("search_metadata")) {
                            Map<String, Object> metadata = (Map<String, Object>) searchResult.get("search_metadata");
                            String status = (String) metadata.get("status");
                            if (!"Success".equals(status)) {
                                logger.warn("搜索API返回非成功状态: {}", status);
                                return new McpSchema.CallToolResult("搜索失败，API返回状态: " + status, true);
                            }
                        }

                        // 提取有机搜索结果
                        List<Map<String, Object>> organicResults = (List<Map<String, Object>>) searchResult.get("organic_results");
                        if (organicResults == null || organicResults.isEmpty()) {
                            return new McpSchema.CallToolResult("无内容", false);
                        }

                        // 直接返回organic_results的原始内容
                        String organicResultsJson = objectMapper.writeValueAsString(organicResults);
                        return new McpSchema.CallToolResult(organicResultsJson, false);

                    } catch (Exception e) {
                        logger.error("解析搜索结果失败", e);
                        // 如果无法解析JSON，直接返回原始响应
                        return new McpSchema.CallToolResult(response, false);
                    }

                } catch (Exception e) {
                    logger.error("联网搜索失败", e);
                    return new McpSchema.CallToolResult("搜索错误: " + e.getMessage(), true);
                }
            }
        );
    }
}
